package com.ffcs.cn.action.base.checkbox;

import com.supermap.desktop.controls.ui.controls.SmDialog;
import com.supermap.desktop.controls.ui.controls.TreeComboBox;
import com.supermap.desktop.core.ui.controls.GridBagConstraintsHelper;
import org.pushingpixels.substance.api.renderers.SubstanceDefaultTreeCellRenderer;

import javax.swing.*;
import javax.swing.tree.DefaultMutableTreeNode;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class DialogTreeComboBoxMultiSelectClose extends SmDialog {

	private JTree tree;
	private JLabel label;
	private TreeComboBox treeComboBox;
	// 带关闭comboBox编辑器，具体看ComboBoxMultiSelectCloseEditor类说明
	private ComboBoxMultiSelectCloseEditor comboBoxMultiSelectCloseEditor = null;

	public DialogTreeComboBoxMultiSelectClose() {
		//设置标题
		setTitle("TreeComboBox 多选示例");
		//设置初始化窗口大小
		Dimension dimension = new Dimension(300, 400);
		setSize(dimension);
		//设置最小窗口
		setMinimumSize(dimension);
		//初始化使用控件
		initComponents();
		//初始化布局，并添加控件
		initLayout();
	}

	private void initComponents() {
		//创建节点
		DefaultMutableTreeNode workspaceNode = new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("工作空间"));

		DefaultMutableTreeNode datasourceNode = new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("数据源"));
		//添加子节点
		datasourceNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("DataSource1")));
		datasourceNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("DataSource2")));
		datasourceNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("DataSource3")));

		DefaultMutableTreeNode mapNode = new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("地图"));
		mapNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Map1")));
		mapNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Map2")));
		mapNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Map3")));

		DefaultMutableTreeNode layoutNode = new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("布局"));
		layoutNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Layout1")));
		DefaultMutableTreeNode defaultMutableTreeNodeLayout2 = new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Layout2"));
		layoutNode.add(defaultMutableTreeNodeLayout2);
		layoutNode.add(new DefaultMutableTreeNode(new ComboBoxSelectableDataItem("Layout3")));

		workspaceNode.add(datasourceNode);
		workspaceNode.add(mapNode);
		workspaceNode.add(layoutNode);

		//创建树
		this.tree = new JTree(workspaceNode);
		//给根节点显示折叠按钮
		this.tree.setShowsRootHandles(true);
		this.label = new JLabel("多选与关闭:");
		// 创建树ComboBox，并设置树
		this.treeComboBox = new TreeComboBox(this.tree){
			// 重写获取选中的数据，因为选中的数据都在Editor加了，所以直接从Editor获取
			@Override
			public Object[] getSelectedItems() {
				return comboBoxMultiSelectCloseEditor.getComboBoxDataItems();
			}
		};
		// 树comboBox开启支持多选
		this.treeComboBox.setSupportMultiSelection(true);
		this.comboBoxMultiSelectCloseEditor = new ComboBoxMultiSelectCloseEditor();
		// treeComboBox支持多选后，默认的comboBox框里显示的是多选的数据没带关闭按钮，所以需要自定义Editor，带上关闭按钮。注意自定义Editor得在开启多选后，因为开启多选时会默认给个Editor
		this.treeComboBox.setEditor(this.comboBoxMultiSelectCloseEditor);
		// 添加ActionListener获取到在comboBox下拉框里点击的数据项，进而设置数据项的状态，并将数据项添加到Editor或从Editor移除
		this.treeComboBox.addActionListener(new ActionListener() {
			@Override
			public void actionPerformed(ActionEvent e) {
				DefaultMutableTreeNode defaultMutableTreeNode = (DefaultMutableTreeNode) treeComboBox.getSelectedItem();
				ComboBoxSelectableDataItem comboBoxSelectableDataItem = (ComboBoxSelectableDataItem) defaultMutableTreeNode.getUserObject();
				comboBoxSelectableDataItem.setSelected(!comboBoxSelectableDataItem.isSelected());
				if (comboBoxSelectableDataItem.isSelected()) {
					addItemObject(comboBoxSelectableDataItem);
				} else {
					removeItemObject(comboBoxSelectableDataItem);
				}
				// 清除树里的选择项，树本身是支持多选的，但每个节点是通过checkbox状态来确定是否选择一个数据，所以树的多选干掉，要不然有两个选择状态也不好同步
				treeComboBox.setSelectedItem(null);
			}
		});
		// 设置cellRender，因为多选comboBox的Editor是自定义的，所以cellRender不需要实现CommonObjectToString接口，需要实现该接口，参见DialogTreeComboBoxMultiSelect
		this.tree.setCellRenderer(new SubstanceDefaultTreeCellRenderer() {
			@Override
			public Component getTreeCellRendererComponent(JTree tree, Object value, boolean sel, boolean expanded, boolean leaf, int row, boolean hasFocus) {
				DefaultMutableTreeNode defaultMutableTreeNode = (DefaultMutableTreeNode) value;
				ComboBoxSelectableDataItem comboBoxSelectableDataItem = (ComboBoxSelectableDataItem) defaultMutableTreeNode.getUserObject();
				PanelSimpleCheck panelSimpleCheck = new PanelSimpleCheck(comboBoxSelectableDataItem);
				return panelSimpleCheck;
			}
		});
	}

	private void initLayout() {
		//设置布局为 GridBagLayout 布局
		this.setLayout(new GridBagLayout());

		this.add(this.label, new GridBagConstraintsHelper(0, 0, 1, 1).setAnchor(GridBagConstraints.WEST).setInsets(GridBagConstraintsHelper.FRAME_CONTROL_GAP, GridBagConstraintsHelper.FRAME_CONTROL_GAP, GridBagConstraintsHelper.CONTROLS_GAP, 0));
		this.add(this.treeComboBox, new GridBagConstraintsHelper(1, 0, 1, 1).setAnchor(GridBagConstraints.EAST).setInsets(GridBagConstraintsHelper.FRAME_CONTROL_GAP, GridBagConstraintsHelper.CONTROLS_GAP, GridBagConstraintsHelper.CONTROLS_GAP, GridBagConstraintsHelper.FRAME_CONTROL_GAP).setWeight(1, 0).setFill(GridBagConstraints.HORIZONTAL));

		this.add(new JPanel(), new GridBagConstraintsHelper(0, 1, 2, 1).setInsets(0, GridBagConstraintsHelper.CONTROLS_GAP, 0, GridBagConstraintsHelper.FRAME_CONTROL_GAP).setFill(GridBagConstraints.BOTH).setWeight(1, 1));
	}

	private void addItemObject(ComboBoxSelectableDataItem comboBoxSelectableDataItem) {
		PanelClose panelClose = new PanelClose(comboBoxSelectableDataItem) {
			@Override
			protected void close(ComboBoxSelectableDataItem comboBoxSelectableDataItem) {
				// 响应点击关闭按钮后，从Editor移除
				removeItemObject(comboBoxSelectableDataItem);
			}
		};
		this.comboBoxMultiSelectCloseEditor.addPanelClose(panelClose);
	}

	private void removeItemObject(ComboBoxSelectableDataItem comboBoxSelectableDataItem) {
		this.comboBoxMultiSelectCloseEditor.removeComboBoxDataItem(comboBoxSelectableDataItem);
	}
}
